home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
SGI Freeware 1998 June
/
SGI Freeware 1998 June.iso
/
dist
/
fw_ATxgopher.idb
/
usr
/
freeware
/
src
/
xgopher.1.3
/
dirList.c.z
/
dirList.c
Wrap
C/C++ Source or Header
|
1998-01-21
|
6KB
|
301 lines
/* dirList.c
routines to manage the data structures for gopher directories */
/*---------------------------------------------------------------*/
/* Xgopher version 1.3 08 April 1993 */
/* version 1.2 20 November 1992 */
/* version 1.1 20 April 1992 */
/* version 1.0 04 March 1992 */
/* X window system client for the University of Minnesota */
/* Internet Gopher System. */
/* Allan Tuchman, University of Illinois at Urbana-Champaign */
/* Computing and Communications Services Office */
/* Copyright 1992, 1993 by */
/* the Board of Trustees of the University of Illinois */
/* Permission is granted to freely copy and redistribute this */
/* software with the copyright notice intact. */
/*---------------------------------------------------------------*/
#include <stdio.h>
#include "gopher.h"
#include "dirList.h"
#include "item.h"
#include "listP.h"
#include "osdep.h"
static gopherDirList unusedDirs = {NULL, NULL};
static int firstDirAlloc = TRUE;
/* Directory list management routines:
acquireDir() return ptr to a gopherDir structure
releaseDir(gopherDirP) Return directory to the free list
previousDir(gopherDirP) return a pointer to previous directory
nextDir(gopherDirP) return a pointer to next directory
freeDirList(gopherDirP) Free a list of directories
allocGopherDir(int) Allocate n new gopher directories
current directory list management:
getCurrentDir() return a ptr to current directory
pushCurrentDir(gopherDirP) Push a new directory to be current
popCurrentDir() make previous directory current
getCurrentDirIndex() return search string of curr directory
noCurrentDir() T/F; does current directory exist
atFirstDir() T/F; is current directory first one
checkDirStack() freeing expired gopher items from stack
*/
/* acquireDir
Allocate a gopher directory from the free list */
gopherDirP
acquireDir()
{
gopherDirP dir;
if (unusedDirs.first == NULL) {
/* out of gopher directories, so allocate more */
allocGopherDir(firstDirAlloc ? dirStart : dirIncrement);
firstDirAlloc = FALSE;
}
dir = unusedDirs.first;
unusedDirs.first = dir->next;
if (unusedDirs.first == NULL) unusedDirs.last = NULL;
dir->previous = dir->next = NULL;
return dir;
}
/* releaseDir
Return a gopher directory to the free list */
void
releaseDir(dir)
gopherDirP dir;
{
dir->next = unusedDirs.first;
unusedDirs.first = dir;
if (unusedDirs.last == NULL) unusedDirs.last = dir;
return;
}
/* previousDir
return a pointer to the directory previous to the given one */
gopherDirP
previousDir(dir)
gopherDirP dir;
{
if (dir == NULL) return NULL;
return dir->previous;
}
/* nextDir
return a pointer to the directory following to the given one*/
gopherDirP
nextDir(dir)
gopherDirP dir;
{
if (dir == NULL) return NULL;
return dir->next;
}
/* freeDirList
Free a list of directories */
static void
freeDirList(dir)
gopherDirP dir;
{
gopherDirP p;
for (p=dir; p->next != NULL; p=p->next) ;
if (unusedDirs.last == NULL) unusedDirs.last = p;
p->next = unusedDirs.first;
unusedDirs.first = dir;
return;
}
/* allocGopherDir
Allocate n new gopher directories, adding them to the free list */
static void
allocGopherDir(n)
int n;
{
gopherDirP dirList, p;
int i;
if (n <= 0) return;
if ((dirList = (gopherDirP) malloc(n * sizeof(gopherDir))) == NULL) {
/* out of memory */
fprintf (stderr, "There is not enough memory to continue.\n");
exit(3);
}
for (i=0, p=dirList; i<n-1; i++, p++) {
p->next = p+1;
}
p->next = NULL;
freeDirList(dirList);
return;
}
/* -----------------------------------------------------------------------
Special section for managing Current directory and the directory stack
----------------------------------------------------------------------- */
static gopherDirP currentDir = NULL; /* current directory pointer */
static gopherDirP firstDir = NULL; /* start of dir stack */
/* getCurrentDir
return a pointer to the current directory */
gopherDirP
getCurrentDir()
{
return currentDir;
}
/* pushCurrentDir
Push a new directory to the stack after the current one and
make the new one current. */
void
pushCurrentDir(dir)
gopherDirP dir;
{
/* check for first directory in stack */
if (currentDir == NULL) {
dir->previous = NULL;
firstDir = dir;
} else {
/* discard "popped" directories, if any */
reallyPopFrom(currentDir->next);
dir->previous = currentDir;
currentDir->next = dir;
}
dir->next = NULL;
currentDir = dir;
return;
}
/* popCurrentDir
Just move back to previous directory. Don't actually
delete the subsequent ones until a new push is done. */
void
popCurrentDir()
{
if (currentDir == NULL) return;
if (currentDir->previous == NULL) return;
currentDir = currentDir->previous;
return;
}
/* reallyPopFrom
discard and reclaim the directories in the stack starting from
the given one */
static void
reallyPopFrom(d)
gopherDirP d;
{
gopherDirP tmp;
while (d != NULL){
tmp = d->next;
freeDir(d);
d = tmp;
}
}
/* getCurrentDirIndex
return a pointer to the index search string of the current directory */
char *
getCurrentDirIndex()
{
return getItemIndex(currentDir->selectorItem);
}
/* atFirstDir
return TRUE is current directory is the first one, FALSE otherwise */
BOOLEAN
atFirstDir()
{
return ((currentDir == NULL) || (currentDir->previous == NULL));
}
/* noCurrentDir
return TRUE is there is no current directory, yet; FALSE otherwise */
BOOLEAN
noCurrentDir()
{
return (currentDir == NULL);
}
/* clearDirStack
wipe out the cirectory stack; set it back to its initial state */
void
clearDirStack()
{
reallyPopFrom(firstDir);
currentDir = NULL;
firstDir = NULL;
}
/* checkDirStack
traverse directory stack freeing expired gopher items */
void
checkDirStack()
{
gopherDirP d;
for (d=firstDir; d != NULL; d = d->next) {
if (d->created != NOT_LOADED) clearDirWhenOld(d);
}
return;
}